﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Configuration;
using System.IO;
using System.Drawing;
using System.Security.Cryptography;
using System.Drawing.Imaging;
using System.Text;
using System.Net;
using System.Net.Sockets;
using System.Web.UI;

namespace FangDuShi_Front.Common
{
    public class GenerateUtil
    {
        
        /// <summary>
        /// 创建文件夹
        /// </summary>
        /// <param name="foldername">相对路径</param>
        public static void addfolder(string foldername)
        {
            //获取文件夹绝对路径
            try
            {
                string url = HttpContext.Current.Server.MapPath(foldername);
                //如果不存在该文件夹就创建
                if (!Directory.Exists(url))
                {
                    Directory.CreateDirectory(url);
                }
            }
            catch (Exception)
            {

            }
        }

        /// <summary>
        /// 返回当前服务器路径
        /// </summary>
        /// <returns></returns>
        public static string GetRootPath(Page p)
        {
            //string servername=HttpContext.Current.Request.ServerVariables["Server_Name"];
            //string serverport = HttpContext.Current.Request.ServerVariables["Server_Port"];
            //if (serverport == "80")
            //{
            //    serverport = "";
            //}
            //else
            //{
            //    serverport = ":" + serverport;

            //}
            //string serverAndPort = "http://"+servername + serverport;
            ////string serverAndPort = "http://" + HttpContext.Current.Request.Url.Authority;
            //string strRoot = HttpContext.Current.Request.ApplicationPath;
            //if (strRoot != "/")
            //{
            //    strRoot += "/";
            //}
            //return serverAndPort + strRoot;
            return p.ResolveUrl("~/");
        }

        /// <summary>
        /// 删除文件
        /// </summary>
        /// <param name="file">绝对路径</param>
        public static void DeleteFileJD(string file)
        {
            if (file.Length == 0) return;
            if (System.IO.File.Exists(file))
                System.IO.File.Delete(file);
        }



        /// <summary>
        /// 获取客户端ip地址
        /// </summary>
        /// <returns></returns>
        public static string GetClientIPv4Address()
        {
            string ipv4 = String.Empty;

            foreach (IPAddress ip in Dns.GetHostAddresses(GetClientIP()))
            {
                if (ip.AddressFamily.ToString() == "InterNetwork")
                {
                    ipv4 = ip.ToString();
                    break;
                }
            }

            if (ipv4 != String.Empty)
            {
                return ipv4;
            }
            // 利用 Dns.GetHostEntry 方法，由获取的 IPv6 位址反查 DNS 纪录，
            // 再逐一判断何者为 IPv4 协议，即可转为 IPv4 位址。
            foreach (IPAddress ip in Dns.GetHostEntry(GetClientIP()).AddressList)
            //foreach (IPAddress ip in Dns.GetHostAddresses(Dns.GetHostName()))
            {
                if (ip.AddressFamily.ToString() == "InterNetwork")
                {
                    ipv4 = ip.ToString();
                    break;
                }
            }

            return ipv4;
        }
        private static string GetClientIP()
        {
            if (null == HttpContext.Current.Request.ServerVariables["HTTP_VIA"])
            {
                return HttpContext.Current.Request.ServerVariables["REMOTE_ADDR"];
            }
            else
            {
                return HttpContext.Current.Request.ServerVariables["HTTP_X_FORWARDED_FOR"];
            }

        }


        #region 验证码
        private static int letterWidth = 20;//单个字体的宽度范围

        private static int letterHeight = 20;//单个字体的高度范围

        // private static int letterCount = 4;//验证码位数

        private static char[] chars = "123456789ABCDEFGHJKMNPQRSTUVWXYZabcdefghjkmnpqrstuvwxyz".ToCharArray();
        private static string[] fonts = { "Arial", "Georgia" };
        /// <summary>
        /// 产生波形滤镜效果
        /// </summary>
        private const double PI = 3.1415926535897932384626433832795;
        private const double PI2 = 6.283185307179586476925286766559;
        /// <summary>
        /// 创建验证码的图片
        /// </summary>
        /// <param name="checkCode"></param>
        /// <returns></returns>
        public static byte[] CreateValidateGraphic(string checkCode)
        {

            int int_ImageWidth = checkCode.Length * letterWidth;
            Random newRandom = new Random();
            Bitmap image = new Bitmap(int_ImageWidth, letterHeight);
            Graphics g = Graphics.FromImage(image);
            try
            {
                //生成随机生成器

                Random random = new Random();
                //白色背景
                g.Clear(System.Drawing.Color.White);
                //画图片的背景噪音线

                for (int i = 0; i < 10; i++)
                {
                    int x1 = random.Next(image.Width);
                    int x2 = random.Next(image.Width);
                    int y1 = random.Next(image.Height);
                    int y2 = random.Next(image.Height);

                    g.DrawLine(new Pen(System.Drawing.Color.Silver), x1, y1, x2, y2);
                }

                //画图片的前景噪音点

                for (int i = 0; i < 10; i++)
                {
                    int x = random.Next(image.Width);
                    int y = random.Next(image.Height);

                    image.SetPixel(x, y, System.Drawing.Color.FromArgb(random.Next()));
                }
                //随机字体和颜色的验证码字符


                int findex;
                for (int int_index = 0; int_index < checkCode.Length; int_index++)
                {
                    findex = newRandom.Next(fonts.Length - 1);
                    string str_char = checkCode.Substring(int_index, 1);
                    Brush newBrush = new SolidBrush(GetRandomColor());
                    Point thePos = new Point(int_index * letterWidth + 1 + newRandom.Next(3), 1 + newRandom.Next(3));
                    g.DrawString(str_char, new System.Drawing.Font(fonts[findex], 12, FontStyle.Bold), newBrush, thePos);
                }
                //灰色边框
                g.DrawRectangle(new Pen(System.Drawing.Color.LightGray, 1), 0, 0, int_ImageWidth - 1, (letterHeight - 1));
                //图片扭曲
                // image = TwistImage(image, true, 3, 4);
                //将生成的图片发回客户端

                MemoryStream ms = new MemoryStream();
                image.Save(ms, ImageFormat.Png);
                return ms.ToArray();
            }
            finally
            {
                //Response.ClearContent(); //需要输出图象信息 要修改HTTP头 
                //Response.ContentType = "image/Png";
                //Response.BinaryWrite(ms.ToArray());
                g.Dispose();
                image.Dispose();
            }
        }
        /// <summary>
        /// 正弦曲线Wave扭曲图片
        /// </summary>
        /// <param name="srcBmp">图片路径</param>
        /// <param name="bXDir">如果扭曲则选择为True</param>
        /// <param name="nMultValue">波形的幅度倍数，越大扭曲的程度越高，一般为3</param>
        /// <param name="dPhase">波形的起始相位，取值区间[0-2*PI)</param>
        /// <returns></returns>
        private static System.Drawing.Bitmap TwistImage(Bitmap srcBmp, bool bXDir, double dMultValue, double dPhase)
        {
            System.Drawing.Bitmap destBmp = new Bitmap(srcBmp.Width, srcBmp.Height);

            // 将位图背景填充为白色
            System.Drawing.Graphics graph = System.Drawing.Graphics.FromImage(destBmp);

            graph.FillRectangle(new SolidBrush(System.Drawing.Color.White), 0, 0, destBmp.Width, destBmp.Height);

            graph.Dispose();

            double dBaseAxisLen = bXDir ? (double)destBmp.Height : (double)destBmp.Width;

            for (int i = 0; i < destBmp.Width; i++)
            {
                for (int j = 0; j < destBmp.Height; j++)
                {
                    double dx = 0;

                    dx = bXDir ? (PI2 * (double)j) / dBaseAxisLen : (PI2 * (double)i) / dBaseAxisLen;

                    dx += dPhase;

                    double dy = Math.Sin(dx);

                    // 取得当前点的颜色
                    int nOldX = 0, nOldY = 0;

                    nOldX = bXDir ? i + (int)(dy * dMultValue) : i;

                    nOldY = bXDir ? j : j + (int)(dy * dMultValue);

                    System.Drawing.Color color = srcBmp.GetPixel(i, j);
                    if (nOldX >= 0 && nOldX < destBmp.Width && nOldY >= 0 && nOldY < destBmp.Height)
                    {
                        destBmp.SetPixel(nOldX, nOldY, color);
                    }
                }
            }
            return destBmp;
        }
        private static System.Drawing.Color GetRandomColor()
        {
            Random RandomNum_First = new Random((int)DateTime.Now.Ticks);
            System.Threading.Thread.Sleep(RandomNum_First.Next(50));
            Random RandomNum_Sencond = new Random((int)DateTime.Now.Ticks);

            //  为了在白色背景上显示，尽量生成深色

            //int int_Red = RandomNum_First.Next(256);
            //int int_Green = RandomNum_Sencond.Next(256);
            //int int_Blue = (int_Red + int_Green > 400) ? 0 : 400 - int_Red - int_Green;
            //int_Blue = (int_Blue > 255) ? 255 : int_Blue;
            int int_Red = RandomNum_First.Next(180);
            int int_Green = RandomNum_Sencond.Next(180);
            int int_Blue = (int_Red + int_Green > 300) ? 0 : 400 - int_Red - int_Green;
            int_Blue = (int_Blue > 255) ? 255 : int_Blue;
            return System.Drawing.Color.FromArgb(int_Red, int_Green, int_Blue);
        }
        //  生成随机数字字符串

        public static string GetRandomNumberString(int int_NumberLength)
        {
            Random random = new Random();
            string validateCode = string.Empty;
            for (int i = 0; i < int_NumberLength; i++)
                validateCode += chars[random.Next(0, chars.Length)].ToString();
            return validateCode;
        }
        #endregion

        #region 指定密钥加密

        /// <summary>
        /// 使用给定密钥字符串加密string
        /// </summary>
        /// <param name="original">原始文字</param>
        /// <param name="fieldName">字段名字</param>
        /// <param name="encoding">字符编码方案</param>
        /// <returns>密文</returns>
        public static string Encrypt(string original, string fieldName)
        {
            fieldName = fieldName.ToUpper();
            string key = "ELINGSOFT" + fieldName;

            byte[] buff = System.Text.Encoding.Default.GetBytes(original);
            byte[] kb = System.Text.Encoding.Default.GetBytes(key);
            return Convert.ToBase64String(Encrypt(buff, kb));
        }
        /// <summary>
        /// 使用给定密钥加密
        /// </summary>
        /// <param name="original">明文</param>
        /// <param name="key">密钥</param>
        /// <returns>密文</returns>
        private static byte[] Encrypt(byte[] original, byte[] key)
        {
            TripleDESCryptoServiceProvider des = new TripleDESCryptoServiceProvider();
            des.Key = MakeMD5(key);
            des.Mode = CipherMode.ECB;

            return des.CreateEncryptor().TransformFinalBlock(original, 0, original.Length);
        }
        /// <summary>
        /// 生成MD5摘要
        /// </summary>
        /// <param name="original">数据源</param>
        /// <returns>摘要</returns>
        private static byte[] MakeMD5(byte[] original)
        {
            MD5CryptoServiceProvider hashmd5 = new MD5CryptoServiceProvider();
            byte[] keyhash = hashmd5.ComputeHash(original);
            hashmd5 = null;
            return keyhash;
        }

        #endregion
        #region 指定密钥解密
        /// <summary>
        /// 使用缺省密钥字符串解密string
        /// </summary>
        /// <param name="original">密文</param>
        /// <returns>明文</returns>
        public static string Decrypt(string original, string fieldName)
        {
            fieldName = fieldName.ToUpper();
            original = original.Replace(" ", "+");//空格替换加号，加号在query string是保留用来代表空格的
            return Decrypt(original, "ELINGSOFT" + fieldName, System.Text.Encoding.Default);
        }
        /// <summary>
        /// 使用给定密钥字符串解密string,返回指定编码方式明文
        /// </summary>
        /// <param name="encrypted">密文</param>
        /// <param name="key">密钥</param>
        /// <param name="encoding">字符编码方案</param>
        /// <returns>明文</returns>
        private static string Decrypt(string encrypted, string key, Encoding encoding)
        {
            byte[] buff = Convert.FromBase64String(encrypted);
            byte[] kb = System.Text.Encoding.Default.GetBytes(key);
            return encoding.GetString(Decrypt(buff, kb));
        }
        /// <summary>
        /// 使用给定密钥解密数据
        /// </summary>
        /// <param name="encrypted">密文</param>
        /// <param name="key">密钥</param>
        /// <returns>明文</returns>
        private static byte[] Decrypt(byte[] encrypted, byte[] key)
        {
            TripleDESCryptoServiceProvider des = new TripleDESCryptoServiceProvider();
            des.Key = MakeMD5(key);
            des.Mode = CipherMode.ECB;

            return des.CreateDecryptor().TransformFinalBlock(encrypted, 0, encrypted.Length);
        }
        #endregion


        /// <summary>
        /// 生成字符串型唯一ID
        /// </summary>
        /// <returns></returns>
        public static string GenerateStringId()
        {
            long i = 1;
            foreach (byte b in Guid.NewGuid().ToByteArray())
            {
                i *= ((int)b + 1);
            }
            string result = string.Format("{0:yyyyMMddHHmmss}", DateTime.Now) + string.Format("{0:x}", i - DateTime.Now.Ticks);
            return result;
        }
        /// <summary>
        /// 创建文件夹
        /// </summary>
        /// <param name="foldername">相对路径</param>
        public static void Addfolder(string foldername)
        {
            //获取文件夹绝对路径
            try
            {
                string url = HttpContext.Current.Server.MapPath(foldername);
                //如果不存在该文件夹就创建
                if (!Directory.Exists(url))
                {
                    Directory.CreateDirectory(url);
                }
            }
            catch (Exception)
            {

            }
        }
        
        /// <summary>
        /// 上传信息类文件
        /// </summary>
        /// <param name="fu"></param>
        /// <param name="url"></param>
        /// <returns></returns>
        //public static string UploadDocFile(HttpPostedFileBase fu, string url, ref Model.SystemNoticeAttach docAttachModel, string docDesc)
        //{
        //    if (fu.ContentLength <= 0)
        //    {
        //        return "1";//文件内容为空
        //    }

        //    //获取文件类型、大小、名称
        //    string type = fu.ContentType;
        //    int size = fu.ContentLength;
        //    string factFileName = Path.GetFileNameWithoutExtension(fu.FileName);

        //    //获取文件的扩展名
        //    string extension = Path.GetExtension(fu.FileName).ToLower();
        //    //switch (extension)
        //    //{
        //    //    case ".jpg": type = "image/pjpeg"; break;
        //    //    case ".gif": type = "image/gif"; break;
        //    //    case ".bmp": type = "image/bm;"; break;
        //    //    case ".png": type = "image/x-png"; break;
        //    //}


        //    //if (type != "image/bmp" && type != "image/gif" && type != "image/pjpeg" && type != "image/x-png" && type != "image/jpg")
        //    //{
        //    //    return "2";//上传类型不是图片
        //    //}

        //    if (size > 100 * 1024 * 1024)
        //    {
        //        return "3";//超出大小100M
        //    }

        //    //改变附件名称
        //    string strnewFileNmae = GenerateUtil.GenerateStringId();
        //    //判断附件保存文件夹是否存在
        //    GenerateUtil.Addfolder(url);
        //    string fullpath = HttpContext.Current.Server.MapPath(url) + "/" + strnewFileNmae + extension;

        //    //判断是否存在相同的文件
        //    if (File.Exists(fullpath) == true)
        //    {
        //        return "4";//文件已存在
        //    }
        //    //上传文件到硬盘
        //    fu.SaveAs(fullpath);

        //    docAttachModel.FAttachSvrFileName = url + "/" + strnewFileNmae + extension;
        //    docAttachModel.FAttachOldFileName = factFileName + extension;
        //    //获取文件二进制格式
        //    System.IO.Stream stream = fu.InputStream;
        //    byte[] buffer = new byte[stream.Length];
        //    stream.Read(buffer, 0, (int)stream.Length);
        //    stream.Close();
        //    docAttachModel.FAttachContent = buffer;
        //    docAttachModel.FAttachFileExt = type;

        //    if (docDesc == "")
        //    {
        //        docAttachModel.FAttachDesc = factFileName;
        //    }
        //    else
        //    {
        //        docAttachModel.FAttachDesc = docDesc;
        //    }
        //    return strnewFileNmae + extension;//文件名称
        //}

        /// <summary>
        /// 删除文件
        /// </summary>
        /// <param name="file">此地路径相对程序路径而言</param>
        public static void DeleteFile(string file)
        {
            if (file.Length == 0) return;
            if (System.IO.File.Exists(System.Web.HttpContext.Current.Server.MapPath(file)))
                System.IO.File.Delete(System.Web.HttpContext.Current.Server.MapPath(file));
        }
        /// <summary>
        /// 获取配置文件appSettings的值
        /// </summary>
        /// <param name="key"></param>
        /// <returns></returns>
        public static string GetConfigValue(string key)
        {
            string value = "";
            if (ConfigurationManager.AppSettings[key] != null)
            {
                value = ConfigurationManager.AppSettings[key].ToString();
            }
            return value;
        }
        /// <summary>
        /// 身份证15位转18位
        /// </summary>
        /// <param name="idCardNo"></param>
        /// <returns></returns>
        public static string IDCard15To18(string idCardNo)
        {
            string _idCardNo = "";
            if (idCardNo.Length == 15)
            {
                int[] wi = new int[] { 7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2, 1 };
                char[] ai = new char[] { '1', '0', 'X', '9', '8', '7', '6', '5', '4', '3', '2' };
                string ls_re = "";
                ls_re = idCardNo.Substring(0, 6) + "19" + idCardNo.Substring(6, 9);
                int ll_sum = 0;
                char ll_code = ' ';
                for (int i = 0; i < 17; i++)
                {
                    ll_sum += wi[i] * int.Parse(ls_re.Substring(i, 1));
                    ll_code = ai[ll_sum % 11];
                }
                ls_re += ll_code;

                _idCardNo = ls_re;
            }
            return _idCardNo;

        }

        /// <summary>
        /// 身份证18位转15位
        /// </summary>
        /// <param name="idCardNo"></param>
        /// <returns></returns>
        public static string IDCard18To15(string idCardNo)
        {
            string _idCardNo = "";
            if (idCardNo.Length == 18)
            {
                string ls_re = "";
                ls_re = idCardNo.Substring(0, 6) + idCardNo.Substring(8, 9);
                _idCardNo = ls_re;
            }
            return _idCardNo;

        }
    }
}